/**
 * Software License, Version 1.0
 * 
 * Copyright 2003 The Trustees of Indiana University.  All rights reserved.
 * 
 *
 *Redistribution and use in source and binary forms, with or without 
 *modification, are permitted provided that the following conditions are met:
 *
 *1) All redistributions of source code must retain the above copyright notice,
 * the list of authors in the original source code, this list of conditions and
 * the disclaimer listed in this license;
 *2) All redistributions in binary form must reproduce the above copyright 
 * notice, this list of conditions and the disclaimer listed in this license in
 * the documentation and/or other materials provided with the distribution;
 *3) Any documentation included with all redistributions must include the 
 * following acknowledgement:
 *
 *"This product includes software developed by the Community Grids Lab. For 
 * further information contact the Community Grids Lab at 
 * http://communitygrids.iu.edu/."
 *
 * Alternatively, this acknowledgement may appear in the software itself, and 
 * wherever such third-party acknowledgments normally appear.
 * 
 *4) The name Indiana University or Community Grids Lab or NaradaBrokering, 
 * shall not be used to endorse or promote products derived from this software 
 * without prior written permission from Indiana University.  For written 
 * permission, please contact the Advanced Research and Technology Institute 
 * ("ARTI") at 351 West 10th Street, Indianapolis, Indiana 46202.
 *5) Products derived from this software may not be called NaradaBrokering, 
 * nor may Indiana University or Community Grids Lab or NaradaBrokering appear
 * in their name, without prior written permission of ARTI.
 * 
 *
 * Indiana University provides no reassurances that the source code provided 
 * does not infringe the patent or any other intellectual property rights of 
 * any other entity.  Indiana University disclaims any liability to any 
 * recipient for claims brought by any other entity based on infringement of 
 * intellectual property rights or otherwise.  
 *
 *LICENSEE UNDERSTANDS THAT SOFTWARE IS PROVIDED "AS IS" FOR WHICH NO 
 *WARRANTIES AS TO CAPABILITIES OR ACCURACY ARE MADE. INDIANA UNIVERSITY GIVES
 *NO WARRANTIES AND MAKES NO REPRESENTATION THAT SOFTWARE IS FREE OF 
 *INFRINGEMENT OF THIRD PARTY PATENT, COPYRIGHT, OR OTHER PROPRIETARY RIGHTS. 
 *INDIANA UNIVERSITY MAKES NO WARRANTIES THAT SOFTWARE IS FREE FROM "BUGS", 
 *"VIRUSES", "TROJAN HORSES", "TRAP DOORS", "WORMS", OR OTHER HARMFUL CODE.  
 *LICENSEE ASSUMES THE ENTIRE RISK AS TO THE PERFORMANCE OF SOFTWARE AND/OR 
 *ASSOCIATED MATERIALS, AND TO THE PERFORMANCE AND VALIDITY OF INFORMATION 
 *GENERATED USING SOFTWARE.
 */
package cgl.narada.performance;

import java.util.Collections;
import java.util.Comparator;
import java.util.Enumeration;
import java.util.Hashtable;
import java.util.Properties;
import java.util.Vector;

import cgl.narada.transport.Link;
import cgl.narada.transport.LinkPerformanceData;
import cgl.narada.transport.sslHttpBase.LinkImpl;
import cgl.narada.transport.sslHttpBase.LinkManager;
import cgl.narada.util.webserver.WebCGI;

/**
 * Title:
 * Description:
 * Company:
 * @author John Yin
 */

public class PerformanceRenderer extends BaseCGI implements WebCGI {

    private StringBuffer m_buffer = new StringBuffer(5000);
    private LinkManager m_channelManager = null;
    private Hashtable      m_comparators = new Hashtable();
    private String         m_url = null;

    /**
     * -------------------------------------------------------------------
     */
    public PerformanceRenderer(String url,LinkManager channelManager) {
        super("Monitoring Service");
        m_channelManager = channelManager;
        m_url = url;
    }

    /**
     * -------------------------------------------------------------------
     */
    public String execute(Properties parameters) {
        refreshFields();

        String sortBy = parameters.getProperty("field");

        Vector channels = new Vector();
        Enumeration e = m_channelManager.getLinks();
        while(e.hasMoreElements()) {
            Link c = (Link)e.nextElement();
            channels.addElement(c);
        }

        if (channels.size() <= 0) {
            return "No channels established";
        }

        if (sortBy == null) {
            sortBy = "avg. latency";
        } else {
            int i = sortBy.indexOf("(");
            if (i > 0) {
                // Remove the () units.
                sortBy = sortBy.substring(0,i);
            }
        }

        Comparator c = (Comparator)m_comparators.get(sortBy);
        if (c == null) {
            return "Invalid comparator";
        }
        Collections.sort(channels,c);
        return printLinks(channels,sortBy);
    }

    /**
     * -------------------------------------------------------------------
     */
    private String printLinks(Vector channels,String sortBy) {
        Link c = (Link)channels.elementAt(0);
        StringBuffer buf = new StringBuffer(10000);
        buf.append(getHeader());
        buf.append("<p class=normal>");
        buf.append("<FORM ACTION='"); buf.append(m_url); buf.append("' METHOD=GET>");
        buf.append("Type: <SELECT name='field' class='normal'>\n");

        LinkPerformanceData[] d = c.getAllPerformanceData();
        for(int i=0;i < d.length;i++) {
            String name = d[i].getPerformanceParameter();
            buf.append("<option ");
            if (name.startsWith(sortBy)) {
                buf.append("selected");
            }
            buf.append(">");
            buf.append(d[i].getPerformanceParameter());
            buf.append("</option>\n");
        }
        buf.append("</select>\n");

        buf.append("<INPUT TYPE=SUBMIT VALUE='Refresh' class='normal'>\n");
        buf.append("<hr>\n");

        buf.append("<table border='0' cellspacing='1' cellpadding='0' width='100%' bgcolor='#0000ff'>\n");
        buf.append("<tr><td align='center'>\n");
	buf.append("<table border='0' cellspacing='1' cellpadding='1' width='100%' bgcolor='#ffffff'>\n");
        buf.append("<tr><td align='center' class='headerW' bgcolor='#777777'>Link</td>\n");
        for(int i=0;i < d.length;i++) {
            String name = d[i].getPerformanceParameter();
            String color = "#000000";
            if (name.startsWith(sortBy)) {
                color = "#006600";
            }
            buf.append("<td align='center' class='headerW' bgcolor='");
            buf.append(color); buf.append("'>");
            buf.append(name);
            buf.append("</td>\n");
        }
        buf.append("</tr>\n");

        Enumeration e = channels.elements();
        while(e.hasMoreElements()) {
            c = (Link)e.nextElement();
            buf.append("<tr><td align='left' class='normal' bgcolor='#999999'>");
            buf.append(c.getLinkType());
            buf.append("/");
            buf.append(c.getLinkId());
            buf.append("</td>\n");
            d = c.getAllPerformanceData();
            for(int i=0;i < d.length;i++) {
                LinkPerformanceData data = d[i];
                buf.append("<td align='center' class='normal' bgcolor='#aaaaaa'>");
                buf.append(data.getParameterValue());
                buf.append("</td>\n");
            }
            buf.append("</tr>");
        }
        buf.append("</table></td></tr></table></p>");

        buf.append("<p><b><u><font class='normal'>Metric Description</font></u></b></p>");
        for(int i=0;i < d.length;i++) {
            buf.append("<b><font class='normal'>");
            buf.append(d[i].getPerformanceParameter());
            buf.append("</b> - ");
            buf.append(d[i].getParameterDescription());
            buf.append("</font><br>");
        }

        buf.append(getFooter());

        return buf.toString();
    }

    /**
     * -------------------------------------------------------------------
     */
    private void refreshFields() {
        Enumeration e = m_channelManager.getLinks();

        try {
            LinkImpl c = (LinkImpl)e.nextElement();
            String[] types = c.getPerformanceFactorsMeasured();
            for(int i=0;i < types.length;i++) {
                Comparator comp = (Comparator)m_comparators.get(types[i]);
                if (comp == null) {
                    m_comparators.put(types[i],new LinkImplComparator(types[i]));
                }
            }
        } catch (Exception ex) {
        }
    }
}
